/*
    SF对象批量操作 查询 修改 删除

    1.选择对象
    2.选择字段
    3.添加筛选条件 
    4.组装sql 
    5.检索
    6.修改
    7.批量导入
    8.批量导出

*/
public with sharing class ObjectBatchOptController {

	public String dataJson {get;private set;}
	public String searchJson {get; set;}
	public String selectObjectName {get; set;}
	public String saveJson {get; set;}
	public String msg {get;private set;}
    public ObjectBatchOptController() {
        
    	//selectObject();
    	getSobjectTypes();
    }


    public void setNil(){
    	dataJson = '[]';
    	saveJson = '[]';
    	selectObjectName = '';
    }

    public void getSobjectTypes(){
    	dataJson = '[]';

    	Set<String> stands = new Set<String>{'Account','Opportunity','Event','Task','Contact','Quote' ,'User' ,'Case' };

    	 ///获取所有对象
    	List<Map<String,Object>> tl = new List<Map<String,Object>>();
		for(Schema.sobjecttype s: Schema.getGlobalDescribe().values()){
                //选择自定义对象//&& s.getDescribe().isSearchable() == true
                    //保存

			Schema.DescribeSObjectResult m = s.getDescribe();
            if( m.IsCustom() == true  || (m.IsCustom() == false  && stands.contains(m.getName()))) {
            	Map<String,Object> d = new Map<String,Object>();
            	d.put('name', m.getName());
            	d.put('label', m.getLabel());
            			    	
            	tl.add(d);
            }
           // System.debug(s.getDescribe().getName())
                
		}
    	dataJson = EncodingUtil.urlEncode(JSON.serialize(tl), 'UTF-8');
    }
    public void selectObject(){
    	dataJson = '[]';
    	msg = '';
    	if(String.isBlank(selectObjectName)){

    		msg = '请选择对象!';
    		return;
    	}

    	SObjectType stype  = Schema.getGlobalDescribe().get(selectObjectName.toLowerCase());
    	if(stype == null){

    		msg = '异常对象!';
    		return;
    	}
    	Schema.DescribeSobjectResult m = stype.getDescribe();
    	List<FieldBean> tmp = new List<FieldBean>();
    	for(String fieldKey : m.fields.getMap().keySet()){
    		tmp.add(new FieldBean(m.fields.getMap().get(fieldKey).getDescribe(),m.getName()));
    	}
    	dataJson = EncodingUtil.urlEncode(JSON.serialize(tmp), 'UTF-8');
    }


    public void query(){
    	dataJson = '[]';
    	msg = '';
    	try {

    		String sql = EncodingUtil.urlDecode(searchJson, 'UTF-8');

	    	Set<String>fields  = new Set<String >();

	    	
	    	Pattern paramPattern  = Pattern.compile('(?<=select).*(?=from)');
	       	Matcher m1 = paramPattern.matcher(sql);
	       	while (m1.find( )) {

	       		 for(String f : m1.group(0).split(',')){
	       		 		if(String.isNotBlank(f))fields.add(f.trim());
	       		 }

	       		 break;
	       	}
	       	System.debug('query=>'+sql);

	       	if(!fields.contains('Id'))fields.add('Id');


	    	List<Map<String,String>> result = new List<Map<String,String>>();
	           for (SObject so  : Database.query(sql)) {
	                Map<String,String> fvMap  = new Map<String,String>();
	               for(String field : fields){
	                    String value = '';
	                    if(field.contains('.')){
	                        
	                        List<String> fcmp= field.split('\\.');

	                        SObject val = so;

	                        for(Integer j = 0 ; j <fcmp.size() ; j ++){
	                            
	                            Object tval =  j < fcmp.size() - 1 ? val.getSObject(fcmp.get(j)) : val.get(fcmp.get(j)) ;
	                            if(tval == null ) break;
	                            if(tval instanceof SObject ){
	                                val = (SObject)tval;
	                            }else{
	                                value = String.valueOf(tval);
	                                break;
	                            }
	                                                    
	                        }
	                    }else{
	                        value = String.valueOf(so.get(field));
	                    }
	                    fvMap.put(field, value);

	               }
	               result.add(fvMap);
	           }

	    	dataJson = EncodingUtil.urlEncode(JSON.serialize(result), 'UTF-8');
    	    
    	}
    	catch (Exception e) {
    	    msg = '查询失败:'+e.getMessage();
    	}
    	
    	

    }

    public void deleteData(){

    	msg = '';
    	List<Object> saveList = (List<Object>) JSON.deserializeUntyped(EncodingUtil.urlDecode(saveJson, 'UTF-8'));
    	List<SObject> sList =new List<SObject>();

    	for(Object o : saveList){
    		Map<String,Object> mo= (Map<String,Object>)o;
    		Id mid = (String)mo.get('Id');
    		SObject so = mid.getSObjectType().newSObject();
    		so.put('Id',mid );
    		sList.add(so);
    	}

    	SavePoint sp = Database.setSavepoint();
    	try {

    		delete sList;
    		msg = '操作成功!';

    	}catch (Exception e) {

    		Database.rollback(sp);
    	  	msg = '操作失败:'+e.getMessage();

    	}

    }
    public void save(){
    	msg = '';
    	try {

    		//解析数据
	    	Map<String,Object> saveMap = (Map<String,Object>) JSON.deserializeUntyped(EncodingUtil.urlDecode(saveJson, 'UTF-8'));
	    	
	    	List<Object> fields =  (List<Object>)saveMap.get('field');

	    	Map<String,String> fieldMap = new Map<String,String>();

	    	for(Object o : fields ){

	    		Map<String,Object> mo= (Map<String,Object>)o;
	    		
	    		String fieldName = (String)mo.get('fieldName');
	    		String fieldType = (String)mo.get('fieldType');

	    		fieldMap.put(fieldName, fieldType);
	    	}


	    	List<Object> saveList = (List<Object>) saveMap.get('data');

	    	List<SObject> sList =new List<SObject>();

	    	for(Object o : saveList){

	    		Map<String,Object> mo= (Map<String,Object>)o;
	    		Id mid = (String)mo.get('Id');
	    		SObject so = mid.getSObjectType().newSObject();
	    		so.put('Id', mid);
	    		for (String fieldKey :  fieldMap.keySet() ) {
	    			so.put(fieldKey,DataUtil.dataHandler(mo.get(fieldKey),fieldMap.get(fieldKey) ) );
	    		}

	    		sList.add(so);

	    	}

	    	SavePoint sp = Database.setSavepoint();
	    	try {

	    		System.debug('save=>'+sList);
	    		update sList;
	    		msg = '保存成功!';

	    	}catch (Exception e) {

	    		Database.rollback(sp);
	    	  	msg = '保存失败:'+e.getMessage();

	    	}
    	    
    	}
    	catch (Exception e) {
    	    msg = '保存失败:'+e.getMessage();
    	}
    	
    	
    

    }
    ///字段 
    public class FieldBean{

    	public String fieldName ;
    	public String fieldLabel ;
    	public String fieldType ;
        public List<Map<String,String>> data;///选项列表
        public String relation;
        public FieldBean reference ;
        public String objname;
        public FieldBean(){}
        public FieldBean(Schema.DescribeFieldResult result,String sobjectName  ){
        	fieldName = result.getName();
            fieldLabel = result.getLabel();
            fieldType = (result.getType()+'').toLowerCase();
            data = new List<Map<String,String>> ();
            relation = result.getRelationshipName();
            objname = sobjectName;

            if(fieldType == 'reference'){
                SObjectType st = result.getReferenceTo().get(0);
                FieldBean fb = new FieldBean();
                fb.fieldName = 'Name';
                fb.fieldLabel = st.getDescribe().getLabel();
                fb.objname = st.getDescribe().getName();
                fb.fieldType = 'string';
                reference = fb ;
            }
        	if(fieldType.contains('picklist')){
                Map<String,String> pickMap = ImportObject.getPicklistValues(sobjectName,fieldName, true);
                for(String k :pickMap.keySet()){
                    Map<String,String> picklist = new Map<String,String>();
                    picklist.put('id', k);
                    picklist.put('text', pickMap.get(k));
                    data.add(picklist);
                }
            }


        }
    }
}